# -*- coding: utf-8 -*-
"""统计分析服务"""

import logging
import random
import os
from datetime import datetime, timedelta
from typing import Dict, List, Any, Tuple

logger = logging.getLogger(__name__)

# 检测运行环境
ENVIRONMENT = os.environ.get('APP_ENV', 'development')
logger.info(f"当前运行环境: {ENVIRONMENT}")

# 标记数据库服务为暂不可用，使用懒加载方式避免循环导入
DB_SERVICE_AVAILABLE = False
DB_SERVICE = None

# 模拟数据生成函数，用于开发环境
def generate_mock_statistics(start_time: datetime, end_time: datetime, camera_id: str = None, realtime: bool = False) -> Dict[str, Any]:
    """生成模拟统计数据"""
    logger.info(f"生成模拟统计数据: {start_time} 到 {end_time}, camera_id: {camera_id}, realtime: {realtime}")
    
    # 计算时间差
    delta = end_time - start_time
    days = delta.days
    
    # 模拟摄像头数据
    cameras = [
        {"id": "cam1", "name": "主路口摄像头"},
        {"id": "cam2", "name": "商业街摄像头"},
        {"id": "cam3", "name": "学校路口摄像头"},
        {"id": "cam4", "name": "高速入口摄像头"}
    ]
    
    if camera_id:
        cameras = [cam for cam in cameras if cam["id"] == camera_id]
    
    # 生成告警趋势数据
    alert_trend = []
    if realtime:
        # 实时数据：每分钟一条
        current_time = start_time
        while current_time <= end_time:
            alert_trend.append({
                "time": current_time.strftime("%H:%M"),
                "count": random.randint(0, 5)
            })
            current_time += timedelta(minutes=1)
    else:
        # 非实时数据：根据时间范围决定粒度
        if days <= 1:
            # 24小时内：每小时一条
            current_time = start_time
            while current_time <= end_time:
                alert_trend.append({
                    "time": current_time.strftime("%H:00"),
                    "count": random.randint(5, 30)
                })
                current_time += timedelta(hours=1)
        elif days <= 7:
            # 7天内：每天一条
            current_time = start_time
            while current_time <= end_time:
                alert_trend.append({
                    "time": current_time.strftime("%m-%d"),
                    "count": random.randint(50, 200)
                })
                current_time += timedelta(days=1)
        else:
            # 30天内：每3天一条
            current_time = start_time
            while current_time <= end_time:
                alert_trend.append({
                    "time": current_time.strftime("%m-%d"),
                    "count": random.randint(100, 500)
                })
                current_time += timedelta(days=3)
    
    # 违规类型分布
    violation_types = [
        {"type": "闯红灯", "count": random.randint(100, 300)},
        {"type": "逆行", "count": random.randint(50, 150)},
        {"type": "超速", "count": random.randint(200, 400)},
        {"type": "违停", "count": random.randint(150, 350)}
    ]
    
    # 计算百分比
    total_violations = sum(v["count"] for v in violation_types)
    for v in violation_types:
        v["percentage"] = round(v["count"] / total_violations * 100, 2)
    
    # 车流量趋势
    traffic_flow = []
    if realtime:
        # 实时数据：每分钟一条
        current_time = start_time
        while current_time <= end_time:
            traffic_flow.append({
                "time": current_time.strftime("%H:%M"),
                "vehicle_count": random.randint(20, 100)
            })
            current_time += timedelta(minutes=1)
    else:
        # 非实时数据：根据时间范围决定粒度
        if days <= 1:
            # 24小时内：每小时一条
            current_time = start_time
            while current_time <= end_time:
                # 模拟早晚高峰
                hour = current_time.hour
                if 7 <= hour <= 9 or 17 <= hour <= 19:
                    count = random.randint(500, 1200)
                else:
                    count = random.randint(200, 800)
                traffic_flow.append({
                    "time": current_time.strftime("%H:00"),
                    "vehicle_count": count
                })
                current_time += timedelta(hours=1)
        elif days <= 7:
            # 7天内：每天一条
            current_time = start_time
            while current_time <= end_time:
                traffic_flow.append({
                    "time": current_time.strftime("%m-%d"),
                    "vehicle_count": random.randint(5000, 15000)
                })
                current_time += timedelta(days=1)
    
    # 时段分布
    time_distribution = []
    for hour in range(24):
        # 模拟时段分布
        if 0 <= hour <= 5:
            count = random.randint(10, 50)
        elif 6 <= hour <= 8 or 17 <= hour <= 19:
            count = random.randint(100, 300)
        else:
            count = random.randint(50, 150)
        time_distribution.append({
            "hour": hour,
            "alert_count": count
        })
    
    # 摄像头详细统计
    camera_stats = []
    for camera in cameras:
        camera_stats.append({
            "camera_id": camera["id"],
            "camera_name": camera["name"],
            "total_alerts": random.randint(200, 800),
            "red_light": random.randint(50, 200),
            "wrong_way": random.randint(30, 100),
            "speeding": random.randint(100, 300),
            "illegal_parking": random.randint(80, 250),
            "vehicle_count": random.randint(10000, 50000),
            "flow_rate": round(random.uniform(100, 800), 2)
        })
    
    # 计算汇总数据
    total_alerts = sum(cam["total_alerts"] for cam in camera_stats)
    total_vehicles = sum(cam["vehicle_count"] for cam in camera_stats)
    average_flow_rate = round(sum(cam["flow_rate"] for cam in camera_stats) / len(camera_stats), 2) if camera_stats else 0
    peak_flow_rate = max(cam["flow_rate"] for cam in camera_stats) if camera_stats else 0
    
    return {
        "total_alerts": total_alerts,
        "total_vehicles": total_vehicles,
        "average_flow_rate": average_flow_rate,
        "peak_flow_rate": peak_flow_rate,
        "alert_trend": alert_trend,
        "violation_types": violation_types,
        "traffic_flow": traffic_flow,
        "time_distribution": time_distribution,
        "camera_stats": camera_stats,
        "cameras": cameras,
        "time_range": {
            "start": start_time.isoformat(),
            "end": end_time.isoformat()
        }
    }

# 实际的统计数据获取函数
def get_statistics_for_time_range(start_time: datetime, end_time: datetime, camera_id: str = None, realtime: bool = False) -> Dict[str, Any]:
    """获取指定时间范围内的统计数据
    
    Args:
        start_time: 开始时间
        end_time: 结束时间
        camera_id: 摄像头ID，可选
        realtime: 是否为实时数据
        
    Returns:
        统计数据字典
    """
    try:
        # 检查环境变量，确定当前运行环境
        app_env = os.environ.get('APP_ENV', 'development')
        logger.info(f"获取统计数据: {start_time} 到 {end_time}, 环境: {app_env}")
        
        # 懒加载数据库服务，避免循环导入
        global DB_SERVICE, DB_SERVICE_AVAILABLE
        if not DB_SERVICE:
            try:
                from database.db_service import db_service as db_instance
                DB_SERVICE = db_instance
                DB_SERVICE_AVAILABLE = True
                logger.info("数据库服务加载成功")
            except ImportError as import_error:
                logger.warning(f"无法导入数据库服务: {str(import_error)}")
                DB_SERVICE_AVAILABLE = False
        
        # 对于生产环境和任何需要真实数据的环境，优先使用数据库
        if (app_env.lower() == 'production' or app_env.lower() == 'staging') and DB_SERVICE_AVAILABLE and DB_SERVICE:
            try:
                # 从数据库获取真实数据
                db_data = DB_SERVICE.get_statistics_data(start_time, end_time, camera_id, realtime)
                
                # 验证返回的数据是否有效
                if db_data and isinstance(db_data, dict):
                    # 检查数据中是否包含关键统计指标
                    if ('total_alerts' in db_data and db_data['total_alerts'] > 0) or \
                       ('camera_stats' in db_data and len(db_data['camera_stats']) > 0):
                        logger.info("成功从数据库获取真实统计数据")
                        return db_data
                    else:
                        logger.warning("数据库返回的数据为空或不完整")
                else:
                    logger.warning("数据库返回的不是有效的数据结构")
            except Exception as db_error:
                logger.error(f"数据库查询失败: {str(db_error)}")
        
        # 开发和测试环境使用模拟数据
        if app_env.lower() == 'development' or app_env.lower() == 'testing':
            logger.info(f"在{app_env}环境中使用模拟数据")
            return generate_mock_statistics(start_time, end_time, camera_id, realtime)
        
        # 其他情况使用模拟数据确保系统正常运行
        logger.warning(f"回退到模拟数据: {app_env}")
        return generate_mock_statistics(start_time, end_time, camera_id, realtime)
        
    except Exception as e:
        logger.error(f"获取统计数据失败: {str(e)}")
        # 最后的备选方案：返回模拟数据以确保系统不崩溃
        return generate_mock_statistics(start_time, end_time, camera_id, realtime)

# 别名，确保函数名称的兼容性
get_statistics_data = get_statistics_for_time_range

# 导出统计数据
def export_statistics_to_csv(statistics_data: Dict[str, Any]) -> str:
    """将统计数据转换为CSV格式"""
    import pandas as pd
    
    # 转换摄像头统计数据为DataFrame
    df = pd.DataFrame(statistics_data['camera_stats'])
    
    # 添加汇总信息
    summary = pd.DataFrame([{
        "camera_id": "汇总",
        "camera_name": "所有摄像头",
        "total_alerts": statistics_data['total_alerts'],
        "red_light": sum(cam["red_light"] for cam in statistics_data['camera_stats']),
        "wrong_way": sum(cam["wrong_way"] for cam in statistics_data['camera_stats']),
        "speeding": sum(cam["speeding"] for cam in statistics_data['camera_stats']),
        "illegal_parking": sum(cam["illegal_parking"] for cam in statistics_data['camera_stats']),
        "vehicle_count": statistics_data['total_vehicles'],
        "flow_rate": statistics_data['average_flow_rate']
    }])
    
    # 合并数据
    result_df = pd.concat([df, summary], ignore_index=True)
    
    # 转换为CSV
    csv_data = result_df.to_csv(index=False, encoding='utf-8-sig')
    
    return csv_data

# 获取实时监控数据
def get_realtime_monitoring_data(camera_id: str = None) -> Dict[str, Any]:
    """获取实时监控数据
    
    从最近5分钟的数据中获取实时监控信息
    在生产环境中优先使用真实数据
    """
    # 获取最近5分钟的数据
    end_time = datetime.now()
    start_time = end_time - timedelta(minutes=5)
    
    logger.info(f"获取实时监控数据，时间范围: {start_time} 到 {end_time}")
    
    # 调用通用的统计数据获取函数，确保生产环境使用真实数据
    return get_statistics_for_time_range(start_time, end_time, camera_id, realtime=True)

# 获取历史趋势数据
def get_historical_trend(start_time: datetime, end_time: datetime, trend_type: str = "alerts") -> List[Dict[str, Any]]:
    """获取历史趋势数据"""
    # 获取统计数据
    statistics_data = get_statistics_for_time_range(start_time, end_time)
    
    # 根据趋势类型返回相应数据
    if trend_type == "alerts":
        return statistics_data["alert_trend"]
    elif trend_type == "traffic":
        return statistics_data["traffic_flow"]
    else:
        return statistics_data["alert_trend"]

# 计算KPI指标
def calculate_kpi_metrics(statistics_data: Dict[str, Any]) -> Dict[str, Any]:
    """计算KPI指标"""
    # 计算各类KPI指标
    total_violations = sum(v["count"] for v in statistics_data["violation_types"])
    
    # 计算处理效率（假设）
    processed_alerts = int(statistics_data["total_alerts"] * 0.85)  # 假设85%的告警已处理
    processing_efficiency = round(processed_alerts / statistics_data["total_alerts"] * 100, 2) if statistics_data["total_alerts"] > 0 else 0
    
    # 计算平均响应时间（假设）
    avg_response_time = round(random.uniform(1, 10), 2)  # 假设平均响应时间在1-10分钟之间
    
    # 计算最高风险区域
    if statistics_data["camera_stats"]:
        highest_risk = max(statistics_data["camera_stats"], key=lambda x: x["total_alerts"])
    else:
        highest_risk = None
    
    return {
        "total_violations": total_violations,
        "processing_efficiency": processing_efficiency,
        "avg_response_time": avg_response_time,
        "highest_risk_area": highest_risk["camera_name"] if highest_risk else "N/A",
        "peak_hour": max(statistics_data["time_distribution"], key=lambda x: x["alert_count"]) if statistics_data["time_distribution"] else None
    }